package org.artifact.core.server;

import cn.hutool.core.net.NetUtil;
import cn.hutool.core.util.StrUtil;
import cn.hutool.http.HttpUtil;
import lombok.Data;
import org.artifact.core.cache.SimpleCache;
import org.artifact.core.cache.SimpleLocalCache;
import org.artifact.core.constant.ArtifactAttrConstant;
import org.artifact.core.context.bytebuf.IByteBuffFactory;
import org.artifact.core.context.id.IDFactory;
import org.artifact.core.context.json.IJsonFactory;
import org.artifact.core.context.session.SessionFactory;
import org.artifact.core.plugin.netty.ProtocolBufferProvider;

@SuppressWarnings("rawtypes")
@Data
public final class ServerContext {

    private ServerContext() {
    }

    private static ServerContext ME = new ServerContext();

    public static ServerContext me() {
        return ME;
    }

    /**
     * 服务器属性
     */
    private SimpleCache<Object,Object> attribute = new SimpleLocalCache();

    /**
     * Json工厂
     */
    private IJsonFactory jsonFactory;

    /**
     * Bytebuffer工厂
     */
    private IByteBuffFactory byteBuffFactory;

    /**
     * ID工厂
     */
    private IDFactory idFactory;

    /**
     * Session工厂
     */
    private SessionFactory sessionFactory;

    /**
     * 协议Buffer工厂
     */
    private ProtocolBufferProvider protocolBufferProvider;

    /**
     * 服务器状态
     */
    private ServerStatusEnum status = ServerStatusEnum.STOP;
//	/**
//	 * Spring上下文
//	 * new FileSystemXmlApplicationContext(path);
//	 * new ClassPathXmlApplicationContext(path);
//	 */
//	private ApplicationContext springContext;

    /** 外网IP */
    public String remoteIP(){
        return attribute.getOrFunction(ArtifactAttrConstant.LOCAL_IP, key -> HttpUtil.get("http://icanhazip.com/").trim()).toString();
    }

    /** 内网IP */
    public String localIP() {
        return attribute.getOrFunction(ArtifactAttrConstant.REMOTE_IP, key -> NetUtil.getLocalhostStr()).toString();
    }

    /** 是否是开发模式 */
    public boolean isDebug() {
        return Boolean.valueOf(attribute.getOrDefault(ArtifactAttrConstant.DEBUG, true).toString());
    }

    /** 服务器ID */
    public String serverId() {
        String serverId = attribute.get(ArtifactAttrConstant.SERVER_ID).toString();
        if (StrUtil.isBlank(serverId)) {
            throw new RuntimeException("not set serverId");
        }
        return serverId;
    }

    /** 项目根包 */
    public String rootPackage() {
        String rootPackage = attribute.get(ArtifactAttrConstant.ROOT_PACKAGE).toString();
        if (StrUtil.isBlank(rootPackage)) {
            throw new RuntimeException("not set rootPackage");
        }
        return rootPackage;
    }

    /** 服务器ID */
    public String serverName() {
        String serverName = attribute.getOrDefault(ArtifactAttrConstant.SERVER_NAME,"").toString();
        return serverName;
    }
}
